/**
 * @Author 赵光
 * @Dsc StringUtils
 * @Date 2020年5月22日
 */
package com.xiaouyudeguang.common.utils;

import java.math.BigDecimal;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * <p>
 * 字符串工具类
 * </p>
 *
 * @author 赵光
 * @since 2019年5月22日
 */
public final class StringUtils {

    public static final String EMPTY = "";

    /**
     * 判断字符串是否为空
     *
     * @param s
     * @return
     */
    /**
     * 对象空判断
     */
    public static boolean isNull(String s) {
        return s == null;
    }

    /**
     * 判断字符串不为空
     *
     * @param s
     * @return
     */
    public static boolean isNotNull(String s) {
        return s != null;
    }

    /**
     * 判断字符串是否为空或空字符串
     *
     * @param s
     * @return
     */
    public static boolean isEmpty(String s) {
        return s == null || EMPTY.equals(s);
    }

    /**
     * 判断字符串不为空或空字符串
     *
     * @param s
     * @return
     */
    public static boolean isNotEmpty(String s) {
        return !isEmpty(s);
    }

    /**
     * 判断字符串是否为空
     *
     * @param s
     * @return
     */
    public static boolean isBlank(String s) {
        return s == null || EMPTY.equals(s);
    }

    /**
     * 判断字符串不为空
     *
     * @param s
     * @return
     */
    public static boolean isNotBlank(String s) {
        return !isBlank(s);
    }

    /**
     * 判断字符串数组是否包含空或空字符串
     *
     * @param sArray
     * @return
     */
    public static boolean anyEmpty(String... sArray) {
        if (sArray == null || sArray.length == 0) {
            return true;
        }
        for (String s : sArray) {
            if (isEmpty(s)) {
                return true;
            }
        }
        return false;
    }

    /**
     * 判断字符串数组参数对象是否都不为空或空字符串
     *
     * @param sArray
     * @return
     */
    public static boolean notEmpty(String... sArray) {
        return Boolean.FALSE == anyEmpty(sArray);
    }

    /**
     * 替换字符
     *
     * @param s
     * @param target
     * @param replacement
     * @return
     */
    public static String replace(String s, CharSequence target, CharSequence replacement) {
        return StringUtils.isBlank(s) ? null : s.replace(target, replacement);
    }

    /**
     * 替换
     *
     * @param text
     * @param props
     * @return
     */
    public static String replaceAll(String text, Map<String, String> props) {
        if (StringUtils.isNotBlank(text) && props != null) {
            for (Entry<String, String> entry : props.entrySet()) {
                text = text.replace(entry.getKey(), entry.getValue());
            }
        }
        return text;
    }

    /**
     * 将对象转化为字符串
     *
     * @param o
     * @return
     * @throws Exception
     */
    public static String valueOf(Object o) {
        return toString(o);
    }

    /**
     * 将对象转化为字符串
     *
     * @param o
     * @return
     * @throws Exception
     */
    public static String toString(Object o) {
        if (o == null) {
            return null;
        }
        if (String.class == o.getClass()) {
            return (String) o;
        }
        if (Number.class.isAssignableFrom(o.getClass())) {
            return String.valueOf(o);
        }
        return JsonObject.toJson(o);
    }

    public static String formatAmount(BigDecimal amount) {
        if (amount == null) {
            amount = BigDecimal.ZERO;
        }
        return formatAmount(amount.toPlainString(), 4);
    }

    /**
     * 如果第一个参数字符串为空，那么返回""
     *
     * @param o
     * @return
     */
    public static String emptyOfNull(Object o) {
        return o == null ? "" : "" + o;
    }

    /**
     * 如果第一个参数字符串为空，那么返回默认值
     *
     * @param value
     * @param defaultValue
     * @return
     */
    public static String defaultOfEmpty(String value, String defaultValue) {
        return isNotEmpty(value) ? value : defaultValue;
    }

    /**
     * 如果第一个参数字符串为空，那么返回默认值
     *
     * @param value
     * @param defaultValue
     * @return
     */
    public static String getOrDefault(String value, String defaultValue) {
        return defaultOfEmpty(value, defaultValue);
    }

    /**
     * 比较相等
     *
     * @param s1
     * @param s2
     * @return
     */
    public static boolean equals(String s1, String s2) {
        return s1 != null && s1.equals(s2);
    }

    /**
     * 比较不相等
     *
     * @param s1
     * @param s2
     * @return
     */
    public static boolean nequals(String s1, String s2) {
        return Boolean.FALSE == equals(s1, s2);
    }

    /**
     * 是否包含
     *
     * @param s1
     * @param s2
     * @return
     */
    public static boolean contains(String s1, String s2) {
        return s1 != null && s2 != null && s1.contains(s2);
    }

    /**
     * 是否不包含
     *
     * @param s1
     * @param s2
     * @return
     */
    public static boolean ncontains(String s1, String s2) {
        return Boolean.FALSE == contains(s1, s2);
    }

    /**
     * 小写字符串第一个字母
     *
     * @param s
     * @return
     */
    public static String toLowCaseFirst(String s) {
        return s.substring(0, 1).toLowerCase() + s.substring(1);
    }

    /**
     * 大写字符串第一个字母
     *
     * @param s
     * @return
     */
    public static String toUpCaseFirst(String s) {
        return s.substring(0, 1).toUpperCase() + s.substring(1);
    }

    /**
     * 字符串补空格
     *
     * @param s
     * @param width
     * @return
     */
    public static String enough(String s, int width) {
        return s.length() >= width ? s : enough(s + " ", width - 1);
    }

    /**
     * 复制字符串到指定长度
     *
     * @param s
     * @param width
     * @return
     */
    public static String copy(String s, int width) {
        return s.length() >= width ? s : copy(s + s, width - 1);
    }

    /**
     * 是否以指定字符开始
     *
     * @param s
     * @param prefix
     * @return
     */
    public static boolean startsWith(String s, String prefix) {
        return isEmpty(s) ? false : s.startsWith(prefix);
    }

    /**
     * 是否以指定字符结束
     *
     * @param s
     * @param suffix
     * @return
     */
    public static boolean endsWith(String s, String suffix) {
        return isEmpty(s) ? false : s.endsWith(suffix);
    }

    /**
     * 计算长度
     *
     * @param s
     * @return
     */
    public static int length(String s) {
        return isEmpty(s) ? 0 : s.length();
    }

    /**
     * list转字符串数组
     *
     * @param list
     * @return
     */
    public static String[] toStringArray(List<String> list) {
        return list == null ? null : list.toArray(new String[list.size()]);
    }

    /**
     * 分割字符串为数组
     *
     * @param s
     * @param regex
     * @return
     */
    public static String[] split(String s, String regex) {
        return isEmpty(s) ? null : s.split(regex);
    }

    /**
     * 分割字符串为list
     *
     * @param s
     * @param regex
     * @return
     */
    public static List<String> splitToList(String s, String regex) {
        return isEmpty(s) ? null : Arrays.asList(s.split(regex));
    }

    /**
     * trim
     *
     * @param s
     * @return
     */
    public static String trim(String s) {
        return isEmpty(s) ? s : s.trim();
    }

    public static String captureName(String name) {
        name = name.substring(0, 1).toUpperCase() + name.substring(1);
        return name;
    }

    public static String lowerName(String name) {
        name = name.substring(0, 1).toLowerCase() + name.substring(1);
        return name;
    }

    public static String putOffUnderline(String columnName) {
        StringBuffer fieldNameBuffer = null;
        String tempNameArray[] = columnName.split("_");
        for (int i = 0; i < tempNameArray.length; i++) {
            if (i == 0) {
                fieldNameBuffer = new StringBuffer(tempNameArray[i]);
            } else {
                fieldNameBuffer.append(captureName(tempNameArray[i]));
            }
        }
        return fieldNameBuffer.toString();
    }

    public static String lowerCamel(String str) {
        str = str.substring(0, 1).toUpperCase() + str.substring(1);
        Matcher matcher = Pattern.compile("[A-Z]").matcher(str);
        StringBuffer sb = new StringBuffer();
        while (matcher.find()) {
            matcher.appendReplacement(sb, "_" + matcher.group(0).toLowerCase());
        }
        matcher.appendTail(sb);
        return sb.substring(1);
    }

    public static String toCharSet(Object obj, String charset) {
        try {
            return obj == null ? null : new String((obj + "").getBytes(charset), charset);
        } catch (Exception e) {
            return null;
        }
    }

    public static String format(Collection<?> collection) {
        StringBuilder sb = new StringBuilder();
        collection.forEach(c -> {
            sb.append(",").append(c);
        });
        return sb.substring(1);
    }

    public static String formatAmount(String str, int len) {
        String[] arr = str.split("\\.");
        if (arr[0].length() < len) {
            return str;
        }
        StringBuilder sb = new StringBuilder(arr[0]);
        for (int i = arr[0].length() - len; i > 0; i -= len) {
            sb.insert(i, ',');
        }
        return sb.append(".").append(arr[1]).toString();
    }

    /**
     * 截取前边的
     *
     * @param str
     * @param text
     * @return
     */
    public static String cut(String str, String text) {
        return str == null || !str.contains(text) ? str : str.substring(0, str.indexOf(text));
    }

    /**
     * 截取前边的(带匹配文本)
     *
     * @param str
     * @param text
     * @return
     */
    public static String cutWith(String str, String text) {
        return str == null || !str.contains(text) ? str : str.substring(0, str.indexOf(text) + text.length());
    }

    /**
     * 截取后边的
     *
     * @param str
     * @param text
     * @return
     */
    public static String cutAfter(String str, String text) {
        return str == null || !str.contains(text) ? str : str.substring(str.indexOf(text) + text.length());
    }

    /**
     * 截取后边的(带匹配文本)
     *
     * @param str
     * @param text
     * @return
     */
    public static String cutAfterWith(String str, String text) {
        return str == null || !str.contains(text) ? str : str.substring(str.indexOf(text));
    }
}
